﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Citi.Scheduler.Domain.Utils;
using System.Data.Objects;
using System.IO;
using System.Configuration;
using System.Diagnostics;
using System.Threading;

namespace Citi.Scheduler.ConsoleUi.RunScheduler
{
    class Program
    {
        private const string EventSource = "Citi Scheduler Service";
        private const string EventLogName = "Citi Scheduler Service";
        private static Domain.RoutineSchedule routineSchedule = new Domain.RoutineSchedule();

        private string ErrorLog
        {
            get
            {
                var tempFolder = Path.GetDirectoryName(ConfigurationManager.AppSettings["TempFolder"]);
                return Path.Combine(tempFolder, "ErrorLog.txt");
            }
        }

        static void Main(string[] args)
        {
            while (true)
            {
                try
                {
                    //Context.SetOverwriteChanges(Context.Instance.RoutineExecutions);
                    //Context.SetOverwriteChanges(Context.Instance.Routines);
                    //Context.SetOverwriteChanges(Context.Instance.RoutineSchedules);
                    //Context.SetOverwriteChanges(Context.Instance.Schedules);
                    //Context.SetOverwriteChanges(Context.Instance.RoutineExecutions);
                    //Context.SetOverwriteChanges(Context.Instance.RoutineOnDemands);

                    Console.WriteLine("{0} Checking routines", DateTime.Now.ToString("dd/MM/yyy HH:mm:ss"));
                    routineSchedule.SendRoutinesToExecutionQueue(true);
                    Console.WriteLine("{0} Finished", DateTime.Now.ToString("dd/MM/yyy HH:mm:ss"));
                    Console.WriteLine();
                }
                catch (Exception e)
                {
                    //LogUtil.PathLogErro = ErrorLog;
                    //LogUtil.LogError(EventLog, e);
                    Console.WriteLine(e.Message);
                }
                finally
                {
                    Thread.Sleep(240000);
                }
            }
        }

        private static void SetOverwriteChanges<T>(ObjectSet<T> objectSet) where T : GeneralAction
        {
            try
            {
                objectSet.MergeOption = MergeOption.OverwriteChanges;
            }
            catch { }
        }
    }

    public class LogUtil
    {
        public static string PathLogErro { get; set; }

        public static void LogError(EventLog eventLog, string message)
        {
            Log(eventLog, message, EventLogEntryType.Error);
        }

        public static void LogError(EventLog eventLog, Exception exception)
        {
            Log(eventLog, GetAllExceptionDetails(exception), EventLogEntryType.Error);
        }

        public static void Log(EventLog eventLog, string message, EventLogEntryType logType)
        {
            try
            {
                eventLog.WriteEntry(message, logType);
            }
            catch { }

            try
            {
                File.AppendAllLines(PathLogErro,
                    new List<string> { string.Format("{0} - {1}: {2}", eventLog.Source, DateTime.Now.ToString("yyyy/MM/dd HH:mm:ss"), message), string.Empty });
            }
            catch { }
        }

        public static string GetAllExceptionDetails(Exception e)
        {
            var errorDescriptionMessage = string.Empty;

            while (e != null)
            {
                errorDescriptionMessage += string.Format("\n Error: {0}. \n Inner Exception: {1}. \n Stack Trace: {2}",
                    e.Message, e.InnerException != null ? e.InnerException.Message : "No data", string.IsNullOrEmpty(e.StackTrace) ? "No data" : e.StackTrace);
                e = e.InnerException;
            }

            return errorDescriptionMessage;
        }
    }
}
